<script lang="tsx">
import { useDesign } from '@/hooks/useDesign';
import { propTypes } from '@/utils/propTypes';
import { ElInput } from 'element-plus';
import { defineComponent, ref, unref, watch } from 'vue';
import { passwordStrength } from 'check-password-strength';

const prefixCls = useDesign().getPrefixCls('input-password');
export default defineComponent({
  name: 'InputPassword',
  props: {
    strength: propTypes.bool.def(false),
    modelValue: propTypes.string.def('')
  },
  setup(props, { slots, expose, emit, attrs }) {
    const textType = ref<'password' | 'text'>('password');
    const valueRef = ref(props.modelValue);

    watch(
      () => valueRef.value,
      (newValue: string) => {
        emit('update:modelValue', newValue);
      }
    );

    watch(
      () => props.modelValue,
      (val: string) => {
        if (val === unref(valueRef)) return;
        valueRef.value = val;
      }
    );

    const getPasswordStrength = () => {
      const val = unref(valueRef);
      const { id } = passwordStrength(val);
      return val ? id : -1;
    };
    return () => (
      <div class={`${prefixCls}`}>
        <ElInput modelValue={valueRef.value} onUpdate:modelValue={(val) => (valueRef.value = val)} showPassword={true} type={unref(textType)} {...attrs} />
        {props.strength && (
          <div class={['relative h-6px mt-10px mb-6px mr-auto ml-auto', `${prefixCls}__bar`]}>
            <div class={`${prefixCls}__bar--fill`} data-score={getPasswordStrength()}></div>
          </div>
        )}
      </div>
    );
  }
});
</script>
<style lang="less" scoped>
@prefix-cls: ~'@{adminNamespace}-input-password';

.@{prefix-cls} {
  :deep(.@{elNamespace}-input__clear) {
    margin-left: 5px;
  }

  &__bar {
    background-color: var(--el-text-color-disabled);
    border-radius: var(--el-border-radius-base);

    &::before,
    &::after {
      position: absolute;
      z-index: 10;
      display: block;
      width: 25%;
      height: inherit;
      background-color: transparent;
      border-color: var(--el-color-white);
      border-style: solid;
      border-width: 0 5px;
      content: '';
    }

    &::before {
      left: 25%;
    }

    &::after {
      right: 25%;
    }

    &--fill {
      position: absolute;
      width: 0;
      height: inherit;
      background-color: transparent;
      border-radius: inherit;
      transition:
        width 0.5s ease-in-out,
        background 0.25s;

      &[data-score='0'] {
        width: 25%;
        background-color: var(--el-color-danger);
      }

      &[data-score='1'] {
        width: 50%;
        background-color: var(--el-color-warning);
      }

      &[data-score='2'] {
        width: 75%;
        background-color: var(--el-color-primary);
      }

      &[data-score='3'] {
        width: 100%;
        background-color: var(--el-color-success);
      }
    }
  }

  &--mini > &__bar {
    border-radius: var(--el-border-radius-small);
  }
}
</style>
